#include "xmlhandler.h"

XMLHandler :: XMLHandler(VecContinentes &vec, VecMisiones &vm):vContinentes(vec),
															  vMisiones(vm){
	
}

bool XMLHandler :: guardarXML(string rutaXML, string rutaImagen){
	
	string filename;
	
	xmlDocPtr doc;
	if(crearXML(doc, rutaImagen)){
		xmlSaveFile(rutaXML.c_str(), doc);
		/*free the document */
		xmlFreeDoc(doc);
		//Free the global variables that may
		//have been allocated by the parser.
		xmlCleanupParser();
		//this is to debug memory for regression tests
		xmlMemoryDump();
			
		return true;
	}
	return false;
}

bool XMLHandler :: cargarXML(string rutaXML, string &rutaImagen){
	
	string aux;
	SaxParser saxParser(vContinentes, aux, vMisiones);
	saxParser.parse_file(rutaXML);
	size_t found = rutaXML.find_last_of("/");
	rutaImagen = rutaXML.substr(0, found+1);
	rutaImagen += aux;
	return true;
}

/* crea la estructura xmlDoc con nodo raiz "name" */
xmlDocPtr XMLHandler :: xml_new_doc (const gchar *name) {

	xmlNodePtr root;
	xmlDocPtr doc;
	
	doc = xmlNewDoc (xmlCharStrdup("1.0"));

	root = xmlNewDocNode (doc, NULL, xmlCharStrdup(name), NULL);
	xmlDocSetRootElement (doc, root);

	return doc;
}

bool XMLHandler :: crearXML(xmlDocPtr &doc, string rutaImagen){
	
	
	xmlNodePtr mapa_node = NULL, continente = NULL, pais = NULL, coneccion = NULL, nodeRutaImagen = NULL;
	char cadena[256];
	
	doc = xmlNewDoc(BAD_CAST "1.0");
	if(doc){
		mapa_node = xmlNewNode(NULL, BAD_CAST "mapa");
		xmlDocSetRootElement(doc, mapa_node);
		
		nodeRutaImagen = xmlNewChild(mapa_node, NULL, xmlCharStrdup("ruta"), NULL);
		xmlSetProp(nodeRutaImagen, BAD_CAST "path", BAD_CAST xmlCharStrdup(rutaImagen.c_str()));
		
		for (int i = 0; i < vContinentes.get_Size(); i++) {
		
			Continente *c = vContinentes.get_Continente(i);
			continente = xmlNewChild(mapa_node, NULL, xmlCharStrdup("continente"), NULL);
			xmlSetProp (continente, xmlCharStrdup("nombre"), xmlCharStrdup(c->get_Nombre().c_str()));
			//bonus
			int bonus = c->get_Bonus();
			sprintf(cadena,"%d",bonus);
			xmlSetProp (continente, xmlCharStrdup("bonus"), BAD_CAST cadena);
	    
			for (int j = 0; j < c->get_CantPaises(); j++) {
	       
				Pais *p = c->get_Pais(j);
				pais = xmlNewChild(continente, NULL, xmlCharStrdup("pais"), NULL);
				//nombre
				xmlSetProp(pais, BAD_CAST "nombre", BAD_CAST xmlCharStrdup(p->get_Nombre().c_str()));
				//radio
				sprintf(cadena,"%d",p->get_Radio());
				xmlSetProp(pais, BAD_CAST "radio", BAD_CAST cadena);
				//pos X e Y
				int x, y;
				p->get_Pos(x,y);
				sprintf(cadena,"%d",x);
				xmlSetProp(pais, BAD_CAST "x", BAD_CAST cadena);
				sprintf(cadena,"%d",y);
				xmlSetProp(pais, BAD_CAST "y", BAD_CAST cadena);
				//escribir nombre o no
				string mostrar;
				if(p->get_MostrarNombre()){
					mostrar.assign("true");
				}
				else mostrar.assign("false");
				xmlSetProp(pais, BAD_CAST "mostrar", BAD_CAST xmlCharStrdup(mostrar.c_str()));
				for(int k = 0; k < p->cantidad_Conecciones(); k++){
					string cNombre, cContinente;
					p->get_Coneccion(k,cNombre,cContinente);
					coneccion = xmlNewChild(pais, NULL, xmlCharStrdup("conexion"), NULL);
					xmlSetProp(coneccion, BAD_CAST "nombre", BAD_CAST xmlCharStrdup(cNombre.c_str()));
					xmlSetProp(coneccion, BAD_CAST "continente", BAD_CAST xmlCharStrdup(cContinente.c_str()));
				}
			}
	    }
		
		xmlNodePtr nodeMision, nodeConquista, nodeEliminacion;
		int tamanio;
		
		nodeMision = xmlNewChild(mapa_node, NULL, xmlCharStrdup("misiones"), NULL);
		tamanio = vMisiones.get_size();
		for(int i = 0; i < tamanio; i++){
			Mision *m = vMisiones.getMision(i);
			string tipo = m->get_tipo();
			if(tipo.compare("conquista") == 0){
				nodeConquista = xmlNewChild(nodeMision, NULL, xmlCharStrdup(tipo.c_str()), NULL);
				xmlSetProp(nodeConquista, BAD_CAST "continente", BAD_CAST xmlCharStrdup(m->getContinente().c_str()));
				xmlSetProp(nodeConquista, BAD_CAST "descripcion", BAD_CAST xmlCharStrdup(m->toString().c_str()));
				sprintf(cadena,"%d",m->getExtras());
				xmlSetProp(nodeConquista, BAD_CAST "extras", BAD_CAST cadena);
			}
			else{
				nodeEliminacion = xmlNewChild(nodeMision, NULL, xmlCharStrdup(tipo.c_str()), NULL);
				xmlSetProp(nodeEliminacion, BAD_CAST "color", BAD_CAST xmlCharStrdup(m->getColor().c_str()));
			}
		}
		
		return true;
	}
	
	return false;
}

void XMLHandler :: xml_new_continente (xmlDocPtr doc, Continente *c) {

	xmlNodePtr root;
	xmlNodePtr node;
	xmlNodePtr nodePais;
	
	/* nodo raiz */
	root = xmlDocGetRootElement (doc);
	
	node = xmlNewChild (root, NULL, xmlCharStrdup("continente"), NULL);
	
	xmlSetProp (node, xmlCharStrdup("nombre"), xmlCharStrdup(c->get_Nombre().c_str()));
	
	char* cadena;
	sprintf(cadena,"%d",c->get_CantPaises());
	
	xmlSetProp (node, xmlCharStrdup("paises"), xmlCharStrdup(cadena));
	
	for(int i = 0; i < c->get_CantPaises(); i++){
		
		Pais *p = c->get_Pais(i);
		nodePais = xmlNewChild (node, NULL, xmlCharStrdup("pais"), NULL);
		//el nombre del pais
		xmlSetProp (nodePais, xmlCharStrdup("nombre"), xmlCharStrdup(p->get_Nombre().c_str()));
			
		//el radio del pais
		sprintf(cadena,"%d",p->get_Radio());
		xmlSetProp (nodePais, xmlCharStrdup("radio"), xmlCharStrdup(cadena));
			
		//las posiciones X e Y
		int x,y;
		p->get_Pos(x,y);
		sprintf(cadena,"%d",x);
		xmlSetProp (nodePais, xmlCharStrdup("x"), xmlCharStrdup(cadena));
		sprintf(cadena,"%d",y);
		xmlSetProp (nodePais, xmlCharStrdup("y"), xmlCharStrdup(cadena));
	
	}
}

void XMLHandler :: xml_new_pais (xmlNodePtr &root, Pais * p){
	
	xmlNodePtr node;
	char* cadena;
	
	node = xmlNewChild (root, NULL, xmlCharStrdup("pais"), NULL);
	//el nombre del pais
	xmlSetProp (node, xmlCharStrdup("nombre"), xmlCharStrdup(p->get_Nombre().c_str()));
	
	//el radio del pais
	sprintf(cadena,"%d",p->get_Radio());
	xmlSetProp (node, xmlCharStrdup("radio"), xmlCharStrdup(cadena));
	
	//las posiciones X e Y
	int x,y;
	p->get_Pos(x,y);
	sprintf(cadena,"%d",x);
	xmlSetProp (node, xmlCharStrdup("x"), xmlCharStrdup(cadena));
	sprintf(cadena,"%d",y);
	xmlSetProp (node, xmlCharStrdup("y"), xmlCharStrdup(cadena));
	
	//las conecciones
	/*
	for(int i = 0; i < p->cantidad_Conecciones(); i++){
		string paisC, continenteC;
		p->get_Coneccion(i,paisC,continenteC);
		xmlNodePtr nodeConeccion = xmlNewChild (node, NULL, xmlCharStrdup("coneccion"), NULL);
		xmlSetProp (nodeConeccion, xmlCharStrdup("pais"), xmlCharStrdup(paisC.c_str()));
		xmlSetProp (nodeConeccion, xmlCharStrdup("continente"), xmlCharStrdup(continenteC.c_str()));
	}
	*/
}


